---
title: Agent State
icon: "lucide/Bot"
description: Render the state of your agent with custom UI components.
---
import { Accordions, Accordion } from "fumadocs-ui/components/accordion";
import { IframeSwitcher } from "@/components/content"
import { Tabs, Tab } from "fumadocs-ui/components/tabs"
import RunAndConnect from "@/snippets/integrations/aws-strands/run-and-connect.mdx"

<IframeSwitcher
  id="agent-state-example"
  exampleUrl="https://feature-viewer.copilotkit.ai/aws-strands/feature/agentic_generative_ui?sidebar=false&chatDefaultOpen=false"
  codeUrl="https://feature-viewer.copilotkit.ai/aws-strands/feature/agentic_generative_ui?view=code&sidebar=false&codeLayout=tabs"
  exampleLabel="Demo"
  codeLabel="Code"
  height="700px"
/>

## What is this?

AWS Strands agents maintain state as they process tasks. CopilotKit allows you to render this state in your application with custom UI components, which we call **Agentic Generative UI**.

## When should I use this?

Rendering the state of your agent in the UI is useful when you want to provide the user with feedback about the overall state of a session. A great example of this
is a situation where a user and an agent are working together to solve a problem. The agent can store a draft in its state which is then rendered in the UI.

## Implementation

<Steps>
  <Step>
    ### Run and connect your agent
    <RunAndConnect components={props.components} />
  </Step>
  <Step>
    ### Setup your AWS Strands agent with state

    Configure your Strands agent to maintain state. Here's an example that tracks searches:

    ```python title="agent/my_agent.py"
    from strands import Agent, Tool
    from typing import TypedDict, List

    # Define the agent state schema
    class SearchItem(TypedDict):
        query: str
        done: bool

    class AgentState(TypedDict):
        searches: List[SearchItem]

    # Create tool that updates state
    @Tool
    def add_search(query: str) -> dict:
        """
        Add a search to the agent's list of searches.

        Args:
            query: The search query to add

        Returns:
            Success status and query
        """
        # Tool implementation - state is automatically updated
        return {"success": True, "query": query}

    # Create agent with state management
    agent = Agent(
        name="searchAgent",
        description="A helpful assistant for storing searches",
        tools=[add_search],
        state_schema=AgentState,
        initial_state={"searches": []},
        instructions="""
        You are a helpful assistant for storing searches.

        IMPORTANT:
        - Use the add_search tool to add a search to the agent's state
        - ONLY USE THE add_search TOOL ONCE FOR A GIVEN QUERY
        """
    )
    ```

  </Step>
  <Step>
    ### Render state of the agent in the chat

    Now we can utilize `useCoAgentStateRender` to render the state of our agent **in the chat**.

    ```tsx title="app/page.tsx"
    // ...
    import { useCoAgentStateRender } from "@copilotkit/react-core";
    // ...

    // Define the state of the agent, should match the state schema of your Strands Agent.
    type AgentState = {
      searches: {
        query: string;
        done: boolean;
      }[];
    };

    function YourMainContent() {
      // ...

      // [!code highlight:13]
      // styles omitted for brevity
      useCoAgentStateRender<AgentState>({
        name: "searchAgent", // MUST match the agent name in your Strands configuration
        render: ({ state }) => (
          <div>
            {state.searches?.map((search, index) => (
              <div key={index}>
                {search.done ? "✅" : "❌"} {search.query}{search.done ? "" : "..."}
              </div>
            ))}
          </div>
        ),
      });

      // ...

      return <div>...</div>;
    }
    ```

    <Callout type="warn" title="Important">
      The `name` parameter must exactly match the agent name you defined in your Strands configuration (e.g., `searchAgent` from above).
    </Callout>

  </Step>
  <Step>
    ### Render state outside of the chat

    You can also render the state of your agent **outside of the chat**. This is useful when you want to render the state of your agent anywhere
    other than the chat.

    ```tsx title="app/page.tsx"
    import { useCoAgent } from "@copilotkit/react-core"; // [!code highlight]
    // ...

    // Define the state of the agent, should match the state schema of your Strands Agent.
    type AgentState = {
      searches: {
        query: string;
        done: boolean;
      }[];
    };

    function YourMainContent() {
      // ...

      // [!code highlight:3]
      const { state } = useCoAgent<AgentState>({
        name: "searchAgent", // MUST match the agent name in your Strands configuration
      })

      // ...

      return (
        <div>
          {/* ... */}
          <div className="flex flex-col gap-2 mt-4">
            {/* [!code highlight:5] */}
            {state.searches?.map((search, index) => (
              <div key={index} className="flex flex-row">
                {search.done ? "✅" : "❌"} {search.query}
              </div>
            ))}
          </div>
        </div>
      )
    }
    ```

    <Callout type="warn" title="Important">
      The `name` parameter must exactly match the agent name you defined in your Strands configuration (e.g., `searchAgent` from above).
    </Callout>

  </Step>
  <Step>
    ### Give it a try!

    You've now created a component that will render the agent's state in the chat.

    <video
      src="https://cdn.copilotkit.ai/docs/copilotkit/images/coagents/agentic-generative-ui.mp4"
      className="rounded-lg shadow-xl"
      loop
      playsInline
      controls
      autoPlay
      muted
    />
  </Step>
</Steps>
